Two-Factor Authentication (2FA) হল একটি নিরাপত্তা পদ্ধতি যেখানে দুটি ভিন্ন উপায়ে ব্যবহারকারীকে যাচাই করা হয়:
- First Factor (Something you know): একটি পাসওয়ার্ড বা PIN।
- Second Factor (Something you have): একটি টোকেন বা মোবাইল ফোনের মাধ্যমে এককালীন পাসওয়ার্ড (OTP)।
Spring Security-তে 2FA বাস্তবায়ন করতে, সাধারণত OTP (One-Time Password) ব্যবহার করা হয় যা ব্যবহারকারীর ফোনে SMS বা একটি অ্যাপ্লিকেশন (যেমন Google Authenticator) মাধ্যমে পাঠানো হয়। Spring Security তে 2FA বাস্তবায়ন করার জন্য একাধিক উপায় রয়েছে। এখানে আমরা একটি উদাহরণ দেখব যেখানে SMS OTP এবং Password ব্যবহার করে 2FA কনফিগার করা হবে।
Maven Dependencies
প্রথমে, আপনার pom.xml ফাইলে প্রয়োজনীয় ডিপেনডেন্সি যুক্ত করুন:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-oauth2-client</artifactId>
</dependency>
<dependency>
<groupId>com.twilio</groupId>
<artifactId>twilio</artifactId>
<version>8.0.0</version> <!-- Twilio for SMS -->
</dependency>
Twilio একটি জনপ্রিয় SMS API সেবা প্রদানকারী। আপনি অন্যান্য SMS প্রদানকারীর API ব্যবহার করতে পারেন।
2FA Flow
- First Step - Username and Password Authentication:
- ব্যবহারকারী তাদের পাসওয়ার্ড প্রবেশ করবে।
- Second Step - OTP Verification:
- সঠিক পাসওয়ার্ড দিলে, একটি OTP ব্যবহারকারীর মোবাইলে পাঠানো হবে।
- Final Authentication:
- OTP সঠিকভাবে প্রবেশ করলে, লগইন সফল হবে।
1. First Step: Username and Password Authentication
Spring Security Configuration for Authentication
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.web.SecurityFilterChain;
@Configuration
public class SecurityConfig {
@Bean
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
http
.authorizeHttpRequests()
.requestMatchers("/login", "/otp").permitAll() // Allow login and OTP verification pages
.anyRequest().authenticated() // Other pages require authentication
.and()
.formLogin()
.loginPage("/login") // Custom login page
.permitAll()
.and()
.logout()
.permitAll();
return http.build();
}
}
Controller for Login Page
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.stereotype.Controller;
@Controller
public class LoginController {
@GetMapping("/login")
public String showLoginPage() {
return "login"; // Return the login page (HTML)
}
}
Login Page (login.html)
<!DOCTYPE html>
<html>
<head>
<title>Login</title>
</head>
<body>
<h2>Login</h2>
<form action="/login" method="post">
<label for="username">Username:</label>
<input type="text" id="username" name="username" required><br>
<label for="password">Password:</label>
<input type="password" id="password" name="password" required><br>
<button type="submit">Login</button>
</form>
</body>
</html>
2. Second Step: OTP Generation and Verification
OTP Service (For SMS Delivery)
import com.twilio.Twilio;
import com.twilio.rest.api.v2010.account.Message;
import com.twilio.type.PhoneNumber;
import org.springframework.stereotype.Service;
@Service
public class OTPService {
// Twilio credentials
public static final String ACCOUNT_SID = "your_account_sid";
public static final String AUTH_TOKEN = "your_auth_token";
public static final String FROM_PHONE = "+1234567890"; // Your Twilio phone number
public OTPService() {
Twilio.init(ACCOUNT_SID, AUTH_TOKEN); // Initialize Twilio API
}
public void sendOTP(String phoneNumber, String otp) {
Message message = Message.creator(
new PhoneNumber(phoneNumber), // To number
new PhoneNumber(FROM_PHONE), // From number
"Your OTP is: " + otp) // OTP message
.create();
}
public String generateOTP() {
int otp = (int) (Math.random() * 9000) + 1000; // Generate a 4-digit OTP
return String.valueOf(otp);
}
}
OTP Controller (To handle OTP generation and verification)
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.HashMap;
import java.util.Map;
@RestController
public class OTPController {
@Autowired
private OTPService otpService;
private Map<String, String> userOTPMap = new HashMap<>();
@PostMapping("/generate-otp")
public String generateOtp(@RequestParam String phoneNumber) {
String otp = otpService.generateOTP();
userOTPMap.put(phoneNumber, otp);
otpService.sendOTP(phoneNumber, otp); // Send OTP to user's phone
return "OTP sent to your phone";
}
@PostMapping("/verify-otp")
public String verifyOtp(@RequestParam String phoneNumber, @RequestParam String otp) {
String storedOtp = userOTPMap.get(phoneNumber);
if (storedOtp != null && storedOtp.equals(otp)) {
return "OTP verified successfully!";
} else {
return "Invalid OTP!";
}
}
}
OTP Page (otp.html)
<!DOCTYPE html>
<html>
<head>
<title>OTP Verification</title>
</head>
<body>
<h2>Enter OTP</h2>
<form action="/verify-otp" method="post">
<label for="phoneNumber">Phone Number:</label>
<input type="text" id="phoneNumber" name="phoneNumber" required><br>
<label for="otp">OTP:</label>
<input type="text" id="otp" name="otp" required><br>
<button type="submit">Verify OTP</button>
</form>
</body>
</html>
3. Final Authentication
Spring Security Configuration for 2FA
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.web.SecurityFilterChain;
@Configuration
public class SecurityConfig {
@Bean
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
http
.authorizeHttpRequests()
.requestMatchers("/login", "/otp", "/generate-otp").permitAll() // Allow login and OTP pages
.anyRequest().authenticated() // Other pages require authentication
.and()
.formLogin()
.loginPage("/login") // Custom login page
.permitAll()
.and()
.logout()
.permitAll();
return http.build();
}
}
উপসংহার
Spring Security তে Two-Factor Authentication (2FA) বাস্তবায়ন করতে, আপনি পাসওয়ার্ড এবং OTP (যেমন SMS বা Authenticator অ্যাপ) ব্যবহার করে নিরাপত্তা স্তর বাড়াতে পারেন। এখানে SMS OTP-এর মাধ্যমে 2FA বাস্তবায়ন করা হয়েছে, তবে আপনি Google Authenticator বা Authy এর মতো অ্যাপ্লিকেশন ব্যবহার করেও একই ধরনের 2FA সেটআপ করতে পারেন।
আপনার অ্যাপ্লিকেশনে 2FA প্রয়োগ করতে আরও কোনও সাহায্য প্রয়োজন হলে, নির্দ্বিধায় জানাতে পারেন!
Read more